package st.business.tepth.business.visitor;

import android.support.annotation.NonNull;

import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.TypeReference;

import io.reactivex.Observable;
import io.reactivex.ObservableSource;
import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.disposables.Disposable;
import io.reactivex.functions.Function;
import io.reactivex.observers.DisposableObserver;
import io.reactivex.schedulers.Schedulers;
import st.business.tepth.base.OnDataConvertListener;
import st.business.tepth.business.bean.FactoryInfo;
import st.business.tepth.business.bean.LocationBean;
import st.business.tepth.config.Url;
import st.business.tepth.manager.UserBean;
import st.shadow.library.core.net.callback.IError;
import st.shadow.library.core.net.callback.ISuccess;
import st.shadow.library.core.net.data.ObjConverter;
import st.shadow.library.core.net.rx.RxRestClient;
import st.shadow.library.core.storage.ShadowPreference;

/**
 * Author: shadow
 * Email:  1025431817@qq.com
 * Time:   2019-03-05 16:53
 */

public class VisitorModel implements VisitorContract.Model {
    @Override
    public Disposable getLocationInfo(String id,
                                      @NonNull final OnDataConvertListener<LocationBean> listener) {
        return RxRestClient.builder()
                .url(Url.GetVisitorInfo)
                .params("id", id)
                .success(new ISuccess() {
                    @Override
                    public void onSuccess(String response) {
                        listener.convert(convertToVisitorLocation(response));
                    }
                })
                .error(new IError() {
                    @Override
                    public void onError(int code, String msg) {
                        listener.error(code, msg);
                    }
                })
                .build()
                .get();
    }

    @Override
    public Disposable getFactoryInfo(final String androidId,
                                     final OnDataConvertListener<FactoryInfo> succeedListener,
                                     final OnDataConvertListener<LocationBean> listener) {
        return RxRestClient.builder()
                .url(Url.GetDeviceBindInfo)
                .params("workbenchNo", androidId)
                .build()
                .flatPost()
                .subscribeOn(Schedulers.io())
                .observeOn(Schedulers.io())
                .flatMap(new Function<String, ObservableSource<String>>() {
                    @Override
                    public ObservableSource<String> apply(String response) throws Exception {
                        JSONObject jsonObject = JSONObject.parseObject(response);
                        int ResultCode = jsonObject.getInteger("code");
                        String ResultMsg = jsonObject.getString("msg");
                        if (0 == ResultCode) {
                            String object = jsonObject.getString("data");
                            FactoryInfo factoryInfo = convertToFactory(object);
                            if (factoryInfo != null) {
                                String bind = factoryInfo.getBindFactory();
                                if (!bind.isEmpty()) {
                                    //将绑定信息缓存到本地
                                    ShadowPreference.addCustomAppProfile("factoryName",
                                            bind);
                                    return RxRestClient.builder()
                                            .url(Url.GetVisitorInfo)
                                            .params("id", androidId)
                                            .build()
                                            .onlyPost();
                                } else {
                                    if (succeedListener != null) {
                                        succeedListener.convert(factoryInfo);
                                    }
                                    return Observable.error(new Throwable("complete"));
                                }
                            } else {
                                return Observable.error(new Throwable(ResultMsg));
                            }


                        } else {
                            return Observable.error(new Throwable(ResultMsg));
                        }

                    }
                })
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribeWith(new DisposableObserver<String>() {

                    @Override
                    public void onNext(String response) {
                        JSONObject jsonObject = JSONObject.parseObject(response);
                        int ResultCode = jsonObject.getInteger("code");
                        String ResultMsg = jsonObject.getString("msg");
                        if (0 == ResultCode) {
                            String object = jsonObject.getString("data");
                            listener.convert(convertToVisitorLocation(object));
                        } else {
                            listener.error(ResultCode, ResultMsg);
                        }
                    }

                    @Override
                    public void onError(Throwable e) {
                        if (!"complete".equals(e.getMessage())) {
                            listener.error(-1, e.getMessage());
                        }
                    }

                    @Override
                    public void onComplete() {

                    }
                });
    }

    @Override
    public Disposable setFactoryInfo(final String androidId, final int factoryId,
                                     final int groupId,
                                     final String factoryName,
                                     final OnDataConvertListener<String> setListener,
                                     final OnDataConvertListener<LocationBean> dataListener) {
        return RxRestClient.builder()
                .url(Url.SetDeviceBindInfo)
                .params("workbenchNo", androidId)
                .params("organizationId", factoryId)
                .params("orgGroupId", groupId)
                .build()
                .flatPost()
                .subscribeOn(Schedulers.io())
                .observeOn(Schedulers.io())
                .flatMap(new Function<String, ObservableSource<String>>() {
                    @Override
                    public ObservableSource<String> apply(String response) throws Exception {
                        JSONObject jsonObject = JSONObject.parseObject(response);
                        int ResultCode = jsonObject.getInteger("code");
                        String ResultMsg = jsonObject.getString("msg");
                        if (0 == ResultCode) {
                            //将绑定信息缓存到本地
                            ShadowPreference.addCustomAppProfile("factoryName",
                                    factoryName);
                            if (setListener != null) {
                                setListener.convert("");
                            }
                            return RxRestClient.builder()
                                    .url(Url.GetVisitorInfo)
                                    .params("id", androidId)
                                    .build()
                                    .onlyPost();
                        } else {
                            return Observable.error(new Throwable(ResultMsg));
                        }

                    }
                })
                .subscribeOn(Schedulers.io())
                .observeOn(AndroidSchedulers.mainThread())
                .subscribeWith(new DisposableObserver<String>() {

                    @Override
                    public void onNext(String response) {
                        JSONObject jsonObject = JSONObject.parseObject(response);
                        int ResultCode = jsonObject.getInteger("code");
                        String ResultMsg = jsonObject.getString("msg");
                        if (0 == ResultCode) {
                            String object = jsonObject.getString("data");
                            dataListener.convert(convertToVisitorLocation(object));
                        } else {
                            dataListener.error(ResultCode, ResultMsg);
                        }
                    }

                    @Override
                    public void onError(Throwable e) {
                        dataListener.error(-1, e.getMessage());
                    }

                    @Override
                    public void onComplete() {

                    }
                });
    }

    @Override
    public Disposable login(String account, String password, int type, final OnDataConvertListener<UserBean> listener) {
        return RxRestClient.builder()
                .url(Url.UserLogin)
                .params("jobNo", account)
                .params("password", password)
                .params("type", type)
                .success(new ISuccess() {
                    @Override
                    public void onSuccess(String response) {
                        listener.convert(convertToUser(response));
                    }
                })
                .error(new IError() {
                    @Override
                    public void onError(int code, String msg) {
                        listener.error(code, msg);
                    }
                })
                .build()
                .get();
    }

    private LocationBean convertToVisitorLocation(String response) {
        return new ObjConverter<LocationBean>().convert(response
                , new TypeReference<LocationBean>() {
                });
    }

    private FactoryInfo convertToFactory(String response) {
        return new ObjConverter<FactoryInfo>().convert(response
                , new TypeReference<FactoryInfo>() {
                });
    }

    private UserBean convertToUser(String response) {
        return new ObjConverter<UserBean>().convert(response
                , new TypeReference<UserBean>() {
                });
    }
}
